package com.wenjunwu.blog.service.impl;

import java.util.ArrayList;
import java.util.Calendar;
import java.util.Date;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import java.util.Map.Entry;
import java.util.regex.Matcher;
import java.util.regex.Pattern;
import java.util.stream.Collectors;

import javax.servlet.http.HttpServletRequest;

import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.security.core.context.SecurityContextHolder;
import org.springframework.security.core.userdetails.UserDetails;
import org.springframework.stereotype.Service;
import org.springframework.util.StringUtils;

import com.github.pagehelper.Page;
import com.github.pagehelper.PageHelper;
import com.wenjunwu.blog.dao.BlogContentDao;
import com.wenjunwu.blog.entity.BlogContent;
import com.wenjunwu.blog.service.BlogContentService;

import redis.clients.jedis.JedisPool;

@Service
public class BlogContentServiceImpl implements BlogContentService {

	@Autowired
	private BlogContentDao blogContentDao;
	
	@Autowired
	private JedisPool jedisPool;

	@Override
	public void save(HttpServletRequest request) {
		UserDetails userDetails = (UserDetails) SecurityContextHolder.getContext().getAuthentication().getPrincipal();
		String title = request.getParameter("articleTitle");
		String summary = request.getParameter("summary");
		String content = request.getParameter("content");
		int et = content.indexOf("src=");
		if (et > 0) {
			content = addClassToImage(content);
		}
		String catagory = request.getParameter("catagory");
		String section = request.getParameter("section");
		String subsection = request.getParameter("subsection");
		BlogContent blogContent = new BlogContent();
		blogContent.setTitle(title);
		blogContent.setAuthor(userDetails.getUsername());
		blogContent.setSourceFrom("orignal");
		blogContent.setSection(section);
		blogContent.setSummary(summary);
		blogContent.setCatagory(catagory);
		blogContent.setContent(content);
		blogContent.setPubDate(new Date());
		blogContent.setCreateTime(new Date());
		blogContent.setStatus("publish");
		long contentId = Calendar.getInstance().getTimeInMillis();
		blogContent.setContentId(contentId);
		if ("imgnav".equals(section)) {
			int s = content.indexOf("src=");
			int e = content.indexOf("width");
			String imgUrl = content.substring(s + 5, e - 2);
			blogContent.setImgUrl(imgUrl);
			// 保证图片导航可以更新，但只保留三笔数据
			Map<String, Object> params = new HashMap<String, Object>();
			params.put("status", "publish");
			params.put("section", section);
			List<BlogContent> list = blogContentDao.selectByParams(params);
			if (!StringUtils.isEmpty(list) && list.size() == 3) {
				BlogContent temblog = list.get(0);
				temblog.setStatus("invalid");
				temblog.setUpdateTime(new Date());
				blogContentDao.updateByPrimaryKey(temblog);
			}
		}
		if (StringUtils.isEmpty(section)) {
			blogContent.setSection(subsection);
		}
		blogContentDao.insert(blogContent);
	}

	@Override
	public List<BlogContent> getBlogsByParams(Map<String, Object> params) {
		return blogContentDao.selectByParams(params);
	}

	@Override
	public Map<String, List<BlogContent>> selectSummarys(Map<String, Object> params, String groupByParam) {
		Map<String, List<BlogContent>> results = null;
		List<BlogContent> contents = blogContentDao.selectSummarys(params);
		if ("catagory".equalsIgnoreCase(groupByParam)) {
			return contents.stream().collect(Collectors.groupingBy(BlogContent::getCatagory));
		}
		if ("section".equalsIgnoreCase(groupByParam)) {
			return contents.stream().collect(Collectors.groupingBy(BlogContent::getSection));
		}
		return results;
	}

	@Override
	public BlogContent selectByPrimaryKey(Long id) {
		BlogContent blogContent = blogContentDao.selectByPrimaryKey(id);
		String vc = jedisPool.getResource().get(String.valueOf(id));
		blogContent.setViewCount(Integer.valueOf(vc));
		return blogContent;
	}

	private static String addClassToImage(String input) {
		final String REGEX = "<img\\s+alt=\\\".*?\\\"\\s+src=\\\"\\w?.*?\\\"\\s+width=\\\".*?\\\"\\s+height=\\\".*?\\\">";
		Pattern p = Pattern.compile(REGEX);
		Matcher m = p.matcher(input);
		Map<String, String> map = new HashMap<String, String>();
		List<String> list = new ArrayList<String>();
		while (m.find()) {
			String substring = input.substring(m.start(), m.end());
			list.add(substring);
		}

		for (int i = 0; i < list.size(); i++) {
			String before = list.get(i);
			int et = before.indexOf("src=");
			String pre = before.substring(0, et);
			String suf = before.substring(et, before.length());
			String after = pre.concat("class=\"img-fluid\" ").concat(suf);
			map.put(before, after);
		}

		String replace = "";
		for (Entry<String, String> str : map.entrySet()) {
			if (input.contains(str.getKey())) {
				replace = input.replace(str.getKey(), str.getValue());
				input = replace;
			}
		}
		return input;
	}

	@Override
	public Page<BlogContent> findBlogPage(int pageNum, int pageSize, Map<String, Object> params) {
		return PageHelper.startPage(pageNum, pageSize).doSelectPage(() -> blogContentDao.selectSummarys(params));
	}

	public int updateByPrimaryKey(BlogContent record) {
		return blogContentDao.updateByPrimaryKey(record);
	}
}
